Enterprise Objects Framework Release 1.1 Copyright ã1995 by NeXT Computer, Inc.  All Rights Reserved.

EOEntity

Inherits From:	NSObject

Declared In:	eoaccess/EOEntity.h

Class Description

An EOEntity represents an external record type, such as a table in a database or a file of records, and associates the external name or definition of the table with an internal name used by its EOModel and by the application. An EOEntity maintains a group of attributes and relationships, which are collectively called properties. These are represented by the EOAttribute and EORelationship classes, respectively; see their specifications for more information.

You usually define entities in your EOModel with the EOModeler application, which is documented in the Enterprise Objects Framework Developer's Guide, Chapter 5, ªUsing EOModeler.º EOEntity objects are primarily used by the Enterprise Objects Framework for mapping tables in the database to enterprise objects; your code will probably make limited use of them unless you're specifically working with models.

Each EOEntity in a model is associated with a specific enterprise object class whose instances are used to represent records (rows) from the database in applications using components at or above the database level of the Enterprise Objects Framework. If an EOEntity doesn't have a specific class associated with it, instances of EOGenericRecord are created.

An EOEntity may be marked as read-only, in which case any changes to rows or objects for that entity made by the database level objects are denied.

You can define an external query for an EOEntity to be used when a selection is attempted with an unrestricted qualifier (one that would select all rows in the entity's table). An external query is sent unaltered to the database server and so can use database-specific features such as stored procedures. External queries are thus useful for hiding records or invoking such database-specific features.

Like the other major modeling classes, EOEntity provides a user dictionary for the application to store any auxiliary information it needs.

Class Properties, Primary Keys, and Locking

An EOEntity's EOAttributes are usually intended to have their values fetched from the database and presented to enterprise object. However, there may be times when you want to define an attribute that your enterprise objects never see; for example, you may have a special attribute used only for locking records during updates, but that means nothing to your objects. To allow this masking of attributes the EOEntity can define an EOAttribute as a class property, meaning that an EODatabaseChannel hands enterprise objects the value for the attribute whenever data is fetched for the object. (Note that ªclass propertyº here has a more specific meaning than the usual definition of ªany quality or characteristic of a class.º) If an EOAttribute isn't defined as a class property the database channel never hands its values to enterprise objects. You use the setClassProperties: method to establish the set of attributes used as class properties.

In addition to being defined as a class property, an EOEntity can define an EOAttribute as being part of its primary key. The values for the attributes composing a primary key must uniquely identify their enterprise object (and hence a row in the entity's table). You define an EOEntity's primary key attributes with the setPrimaryKeyAttributes: method.

Finally, to support locking of records during updating, an EOEntity defines a set of attributes to be recorded in snapshots any time an enterprise object is fetched. These attributes are compared when an object is updated according to the descriptions in the EODatabaseContext class specification. You establish the set of attributes used for locking with the setAttributesUsedForLocking: method. Note that an attribute used for locking doesn't have to be a class property; it will be recorded in the snapshot, but the enterprise object won't see it.

EOEntity provides methods for checking whether an attribute can be used in a primary key or for locking. Only attributes corresponding directly to a column in the database server's table are eligible for these purposesÐflattened and derived attributes can't be used as a primary key or for locking. The methods for checking are isValidPrimaryKeyAttribute: and isValidAttributeUsedForLocking:. You can also check whether a given property can be defined as a class property with the isValidClassProperty:.

Creating an Entity

An EOEntity requires at least the following to be usable:

·	A name
·	The name of a table in the database (the external name)
·	The name of an enterprise object class
·	A set of attributes to be used as the primary key

Note that if an entity has no enterprise object class name, the database-level objects use EOGenericRecord. Even so, it's best to explicitly name the class when you create the entity. This code excerpt gives an example of creating an EOEntity and adding it to an EOModel:

EOModel *myModel;          /* Assume this exists. */
NSArray *keyAttributes;    /* Assume this exists. */
EOEntity *employeeEntity;

employeeEntity = [[[EOEntity alloc] initWithName:@"employee"]
    autorelease];
[employeeEntity setExternalName:@"EMPLOYEE"];
[employeeEntity setClassName:"Employee"];

/* Create at least the primary key attributes. */

[employeeEntity setPrimaryKeyAttributes:keyAttributes];

Instance Variables

None declared in this class.

Method Types

Initializing instances	- initWithName:

Setting the name	- setName:
- name
+ isValidName:

Getting the model	- model

Getting the qualifier	- qualifier

Accessing attributes	- addAttribute:
- removeAttributeNamed:
- attributeNamed:
- attributes

Accessing relationships	- addRelationship:
- removeRelationshipNamed:
- relationshipNamed:
- relationships

Checking property references	- referencesProperty:

Setting primary key attributes	- setPrimaryKeyAttributes:
- primaryKeyAttributes
- primaryKeyAttributeNames
- isValidPrimaryKeyAttribute:

Getting primary keys	- primaryKeyForRow:

Setting class properties	- setClassProperties:
- classProperties
- classPropertyNames
- isValidClassProperty:

Setting locking attributes	- setAttributesUsedForLocking:
- attributesUsedForLocking
- isValidAttributeUsedForLocking:

Setting the enterprise object class
- setClassName:
- className

Setting external information	- setExternalName:
- externalName

Setting the external query	- setExternalQuery:
- externalQuery

Setting read-only status	- setReadOnly:
- isReadOnly

Setting the user dictionary	- setUserDictionary:
- userDictionary

Class Methods

isValidName:

+ (BOOL)isValidName:(NSString *)name

Returns YES if name is a legal name for an entity, attribute, or relationship, NO otherwise. A legal name contains only the following characters:

First character	any alphanumeric, @, _, #
Remaining characters	as above plus $

Here are some examples of valid and invalid names:

Valid	Invalid

Employee	Employee(temp)
toDepartment	to-Department
@delivered	delivered?
salary$	$salary

Instance Methods

addAttribute:

- (BOOL)addAttribute:(EOAttribute *)anAttribute

Adds anAttribute to the entity and returns YES on success, NO if anAttribute's name is already in use by another attribute or relationship. Sets anAttribute's entity to self.

See also:  - removeAttributeNamed:, - attributeNamed:, - setEntity: (EOAttribute)

addRelationship:

- (BOOL)addRelationship:(EORelationship *)aRelationship

Adds aRelationship to the entity and returns YES on success, NO if aRelationship's name is already in use by another attribute or relationship. Sets aRelationship's entity to self.

See also:  - removeRelationshipNamed:, - relationshipNamed:, - setEntity: (EORelationship)

attributeNamed:

- (EOAttribute *)attributeNamed:(NSString *)name

Returns the attribute named name, or nil if no such attribute exists.

See also:  - attributes, - relationshipNamed:

attributes

- (NSArray *)attributes

Returns the entity's attributes, or nil if the entity has none.

attributesUsedForLocking

- (NSArray *)attributesUsedForLocking

Returns the attributes whose values are compared when a database-level object performs an update with locking (that is, if the EOUpdateWithPessimisticLocking or EOUpdateWithOptimisticLocking update strategies are used). When the database-level classes fetch an enterprise object, they cache these attributes' values in a snapshot. Later, when the enterprise object is updated, the values of these attributes in the object are checked with those in the snapshotÐif they differ, the update fails. See the EODatabaseContext class specification for more information.

className

- (const char *)className

Returns the name of the enterprise object class associated with the entity. When a row is fetched for the entity by an EODatabaseChannel, it's returned as an instance of this class. This class might not be present in the run-time system, and in fact your application may have to load it on demand. If your application doesn't load a class, EOGenericRecord is used.

An enterprise object class other than EOGenericRecord can be mapped to only one entity.

See also:  - databaseChannel:failedToLookupClassNamed: (EODatabaseChannel, ªMethods Implemented by the Delegateº)

classProperties

- (NSArray *)classProperties

Returns the properties bound to the entity's enterprise object class. An entity may have many properties, but only the class properties are actually passed to enterprise objects (and therefore made visible in your application).

See also:  - classPropertyNames

classPropertyNames

- (NSArray *)classPropertyNames

Returns the names of all the properties returned by classProperties.

externalName

- (NSString *)externalName

Returns the name of the entity as understood by the database server.

externalQuery

- (NSString *)externalQuery

Returns a SQL SELECT statement that an EOAdaptorChannel uses to select rows for the entity when a qualifier is empty, or nil if the entity has no external query. An empty qualifier is one that specifies only the entity, and would thus fetch all enterprise objects for that entity.

External queries are useful for hiding records or invoking database-specific features such as stored procedures when an application attempts to select all records for an entity.

See also:  - isEmpty (EOQualifier), - selectAttributes:describedByQualifier:fetchOrder:lock: (EOAdaptorChannel)

initWithName:

- initWithName:(NSString *)name

Initializes a newly allocated EOEntity with name as its internal name. To be usable the EOEntity must have a set of attributes and belong to a model. This is the designated initializer for the EOEntity class. Returns self.

See also:  - addAttribute:, - addEntity: (EOModel)

isReadOnly

- (BOOL)isReadOnly

Returns YES if the entity can't be modified, NO if it can. If an entity can't be modified, then enterprise objects fetched for that entity also can't be modified (inserted, deleted, or updated).

isValidAttributeUsedForLocking:

- (BOOL)isValidAttributeUsedForLocking:(EOAttribute *)anAttribute

Returns NO if anAttribute isn't an EOAttribute, if the EOAttribute doesn't belong to the entity, or if anAttribute is derived. Otherwise returns YES. An attribute that isn't valid for locking will cause setAttributesUsedForLocking: to fail.

isValidClassProperty:

- (BOOL)isValidClassProperty:aProperty

Returns NO if either aProperty isn't an EOAttribute or EORelationship, or if aProperty doesn't belong to the entity. Otherwise returns YES.

isValidPrimaryKeyAttribute:

- (BOOL)isValidPrimaryKeyAttribute:(EOAttribute *)anAttribute

Returns NO if anAttribute isn't an EOAttribute or if anAttribute isn't a simple attribute of the entity (that is, if it's derived or flattened). Otherwise returns YES.

model

- (EOModel *)model

Returns the model that contains the entity.

See also:  - addEntity: (EOModel)

name

- (NSString *)name

Returns the entity's name.

primaryKeyAttributes

- (NSArray *)primaryKeyAttributes

Returns the EOAttributes that make up the primary key for the entity.

See also:  - primaryKeyAttributeNames

primaryKeyAttributeNames

- (NSArray *)primaryKeyAttributeNames

Returns the NSStrings naming the attributes that make up the primary key for the entity.

primaryKeyForRow:

- (NSDictionary *)primaryKeyForRow:(NSDictionary *)aRow

Returns the primary key for aRow, or nil if the primary key can't be computed. The primary key is an NSDictionary whose keys are attribute names and whose values are values for those attributes (note that ªkeyº is used in two senses here).

qualifier

- (EOQualifier *)qualifier

Returns a qualifier for the entity that can be used in EOAdaptorChannel's selectAttributes:describedByQualifier:fetchOrder:lock: method or EODatabaseChannel's selectObjectsDescribedByQualifier:fetchOrder: method. Such a qualifier will select all rows for the entity.

referencesProperty:

- (BOOL)referencesProperty:aProperty

Returns YES if any of the entity's attributes or relationships reference aProperty, NO otherwise. A property can be referenced by a flattened attribute or by a relationship. For example, suppose a model has an Employee entity with a toDepartment relationship. If you flatten the department's name attribute into the Employee entity, creating a departmentName attribute, that flattened attribute references the toDepartment relationship.

If an entity has any outstanding references to a property, you shouldn't remove the property.

See also:  - removeAttributeNamed:, - removeRelationshipNamed:

relationshipNamed:

- (EORelationship *)relationshipNamed:(NSString *)name

Returns the relationship named name, or nil if the entity has no such relationship.

See also:  - relationships, - attributeNamed:

relationships

- (NSArray *)relationships

Returns the entity's relationships, or nil if the entity has none.

removeAttributeNamed:

- (void)removeAttributeNamed:(NSString *)name

Removes the attribute named name if it exists. You should always use referencesProperty: to check that an attribute isn't referenced by another property before removing it.

removeRelationshipNamed:

- (void)removeRelationshipNamed:(NSString *)name

Removes the relationship named name if it exists. You should always use referencesProperty: to check that a relationship isn't referenced by another property before removing it.

setAttributesUsedForLocking:

- (BOOL)setAttributesUsedForLocking:(NSArray *)attributes

Sets attributes as the attributes used when an EODatabaseChannel locks enterprise objects for updates. Returns YES on success and NO if the entity responds NO to isValidAttributeUsedForLocking: for any of the objects in the array. See the EODatabase, EODatabaseContext, and EODatabaseChannel class specifications for information on locking.

setClassName:

- (void)setClassName:(const char *)name

Sets the name of the class associated with the entity to name. This class need not be present in the run-time system when this message is sent. When an EODatabaseChannel fetches objects for the entity, they're created as instances of this class. Your application may have to load the class on demand if it isn't present in the run-time system; if it doesn't load the class, EOGenericRecord will be used.

Note:  If you set the class name to NULL, the className method returns ªEOGenericRecordº.

An enterprise object class other than EOGenericRecord can be mapped to only one entity.

See also:  - databaseChannel:failedToLookupClassNamed: (EODatabaseChannel, ªMethods Implemented by the Delegateº)

setClassProperties:

- (BOOL)setClassProperties:(NSArray *)properties

Sets the entity's class properties to the EOAttributes and EORelationships in properties. Returns YES on success, NO if the entity responds NO to isValidClassProperty: for any of the objects in the array.

setExternalName:

- (void)setExternalName:(NSString *)name

Sets the name of the entity used with the database server to name. For example, though your application may know the entity as ªJobTitleº the database may require a form such as ªJOB_TTLº. An adaptor uses the external name to communicate with the database; your application should never need to use the external name.

setExternalQuery:

- (void)setExternalQuery:(NSString *)aQuery

Sets aQuery as the SQL SELECT statement that an EOAdaptorChannel uses to select rows for the entity when a qualifier is unrestricted. An unrestricted qualifier is one that specifies only the entity, and would thus fetch all enterprise objects for that entity.

External queries are useful for hiding records or invoking database-specific features such as stored procedures when an application attempts to select all records for an entity.

An external query is sent unaltered to the database server, and so must contain the external (column) names instead of the names of EOAttributes. However, to work properly with the adaptor the external query must use the columns in alphabetical order by their corresponding EOAttributes' names.

See also:  - isEmpty (EOQualifier), - selectAttributes:describedByQualifier:fetchOrder:lock: (EOAdaptorChannel)

setName:

- (BOOL)setName:(NSString *)name

Sets the entity's name to name and returns YES on success, NO if name is in use by another entity in the same EOModel.

setPrimaryKeyAttributes:

- (BOOL)setPrimaryKeyAttributes:(NSArray *)keys

Sets the primary key attributes to the attributes in keys. Returns YES on success, or NO if the entity responds NO to isValidPrimaryKeyAttribute: for any of the objects in the array.

You should exercise care in choosing primary key attributes. Floating-point numbers, for example, can't be reliably compared for equality, and are thus unsuitable for use in primary keys. Integer and string types are the safest choice for primary keys.

setReadOnly:

- (void)setReadOnly:(BOOL)flag

Sets according to flag whether the database rows for the entity can be modified by the database level objects.

setUserDictionary:

- (void)setUserDictionary:(NSDictionary *)aDictionary

Sets the dictionary of auxiliary data, which your application can use for whatever it needs. The dictionary must be a property list (that is, it must contain only NSString, NSData, NSArray, and NSString objects).

userDictionary

- (NSDictionary *)userDictionary

Returns a dictionary of user data. Your application can use this to store any auxiliary information it needs. This dictionary is a property list (that is, it contains only NSString, NSData, NSArray, and NSString objects).